package com.promise.jokerdream.work.mercenary

import com.promise.jokerdream.database.entity.MercenaryDispatchGameConfigEntity
import com.promise.jokerdream.config.game.MercenaryTaskType
import com.promise.jokerdream.manager.ExecutionHistoryManager
import com.promise.jokerdream.model.task.MercenaryTaskModel
import com.promise.jokerdream.repository.GameApi
import com.promise.jokerdream.repository.foldWithApiException
import com.promise.jokerdream.response.pc.QueryMercenaryDispatchPCResponse
import com.promise.jokerdream.utils.AppContext
import com.promise.jokerdream.work.BaseWork
import com.promise.jokerdream.work.WorkResult

// 佣兵派遣工作
class MercenaryDispatchWork(
    private val config: MercenaryDispatchGameConfigEntity,
    uin: String
): BaseWork(uin) {

    private val gameApi = GameApi.Companion.getInstance()
    private val historyManager by lazy { ExecutionHistoryManager.Companion.getInstance(AppContext.get()) }

    override val name: String
        get() = "佣兵派遣"

    override suspend fun executeWork(): WorkResult {
        return try {
            // 1. 查询当前状态
            val queryResult = gameApi.queryMercenaryDispatch()
            queryResult.foldWithApiException(
                onSuccess = { response ->
                    processMercenaryDispatch(response)
                },
                onFailure = { code, msg ->
                    historyManager.addHistory(name, msg)
                    return WorkResult.Failure(Exception(msg), msg)
                }
            )
        } catch (e: Exception) {
            historyManager.addHistory(name, e.message)
            WorkResult.Failure(e, e.message)
        }
    }

    /**
     * 处理佣兵派遣逻辑 - 状态机模式
     */
    private suspend fun processMercenaryDispatch(response: QueryMercenaryDispatchPCResponse): WorkResult {
        var currentResponse = response
        var hasChanges = true
        val maxIterations = 100 // 防止无限循环
        var iterationCount = 0

        while (hasChanges && iterationCount < maxIterations) {
            hasChanges = false
            iterationCount++

            // 1. 检查是否有已完成的任务需要领取奖励
            var hasClaimedReward = false
            for (mission in currentResponse.acceptedMissionInfo) {
                if (mission.remainTime == 0) {
                    val claimResult = gameApi.claimMercenaryReward(mission.missionId)
                    claimResult.foldWithApiException(
                        onSuccess = { claimResponse ->
                            historyManager.addHistory(name, claimResponse.getDescription())
                            hasChanges = true
                            hasClaimedReward = true
                        },
                        onFailure = { code, msg ->
                            historyManager.addHistory(name, msg)
                        }
                    )
                }
            }

            // 如果有领取过奖励，先重新查询状态
            if (hasClaimedReward) {
                val newQueryResult = gameApi.queryMercenaryDispatch()
                newQueryResult.foldWithApiException(
                    onSuccess = { newResponse ->
                        currentResponse = newResponse
                    },
                    onFailure = { code, msg ->
                        historyManager.addHistory(name, msg)
                        return WorkResult.Failure(Exception(msg), msg)
                    }
                )
                continue // 重新开始循环，检查新的状态
            }

            // 2. 检查是否可以接受新任务（最多3个）
            val maxConcurrentTasks = 3
            if (currentResponse.acceptedMissionInfo.count() < maxConcurrentTasks && currentResponse.acceptedMissionNum < currentResponse.dayMissionNum) {
                // 查找所有符合配置的任务类型
                val matchingTasks = findAllMatchingTasks(currentResponse.standyMissionInfo)
                if (matchingTasks.isNotEmpty()) {
                    // 逐个尝试执行任务，直到达到最大并发数
                    val remainingSlots = maxConcurrentTasks - currentResponse.acceptedMissionInfo.count()
                    var executedCount = 0

                    for (task in matchingTasks) {
                        if (executedCount >= remainingSlots) break

                        // 快速设置佣兵
                        val setupResult = gameApi.quickSetupMercenary(task.missionId)
                        setupResult.foldWithApiException(
                            onSuccess = { setupResponse ->
                                // 开始任务
                                val beginResult = gameApi.beginMercenaryMission(task.missionId)
                                beginResult.foldWithApiException(
                                    onSuccess = { beginResponse ->
                                        historyManager.addHistory(name, beginResponse.getDescription())
                                        hasChanges = true
                                        executedCount++
                                    },
                                    onFailure = { code, msg ->
                                        historyManager.addHistory(name, msg)
                                    }
                                )
                            },
                            onFailure = { code, msg ->
                                historyManager.addHistory(name, msg)
                            }
                        )
                    }

                    // 如果执行了任务，重新查询状态
                    if (hasChanges) {
                        val newQueryResult = gameApi.queryMercenaryDispatch()
                        newQueryResult.foldWithApiException(
                            onSuccess = { newResponse ->
                                currentResponse = newResponse
                            },
                            onFailure = { code, msg ->
                                historyManager.addHistory(name, msg)
                                return WorkResult.Failure(Exception(msg), msg)
                            }
                        )
                        continue
                    }
                } else {
                    // 没有符合条件的任务，检查是否可以刷新
                    if (currentResponse.refreshDoudouNum == 0) {
                        // 有免费刷新次数，执行刷新
                        val refreshResult = gameApi.refreshMercenaryDispatch()
                        refreshResult.foldWithApiException(
                            onSuccess = { refreshResponse ->
                                currentResponse = refreshResponse
                                hasChanges = true
                            },
                            onFailure = { code, msg ->
                                historyManager.addHistory(name, msg)
                            }
                        )
                    } else {
                        // 没有免费刷新次数，退出循环
                        break
                    }
                }
            } else {
                // 已达到最大任务数或每日上限，退出循环
                break
            }
        }

        return WorkResult.Success
    }


    /**
     * 查找所有符合配置的任务
     * 按优先级排序：S级 > A级 > B级
     * 只返回 accepted=0 的任务（未接受状态）
     */
    private fun findAllMatchingTasks(standyMissions: List<MercenaryTaskModel>): List<MercenaryTaskModel> {
        val matchingTasks = mutableListOf<MercenaryTaskModel>()

        // 根据配置选择的任务类型，按优先级排序
        val selectedTaskTypesSet = if (config.selectedTaskTypes.isEmpty()) emptySet() else config.selectedTaskTypes.split(",").mapNotNull { taskTypeStr -> try { MercenaryTaskType.valueOf(taskTypeStr.trim()) } catch (e: Exception) { null } }.toSet()
        if (MercenaryTaskType.S_LEVEL in selectedTaskTypesSet) {
            val sLevelTasks = standyMissions.filter { it.type == 1 && it.accepted == 0 }
            matchingTasks.addAll(sLevelTasks)
        }

        if (MercenaryTaskType.A_LEVEL in selectedTaskTypesSet) {
            val aLevelTasks = standyMissions.filter { it.type == 2 && it.accepted == 0 }
            matchingTasks.addAll(aLevelTasks)
        }

        if (MercenaryTaskType.B_LEVEL in selectedTaskTypesSet) {
            val bLevelTasks = standyMissions.filter { it.type == 3 && it.accepted == 0 }
            matchingTasks.addAll(bLevelTasks)
        }

        return matchingTasks
    }

    /**
     * 查找符合配置的任务（单个）
     * 优先选择更高级别的任务（S级 > A级 > B级）
     */
    private fun findMatchingTask(standyMissions: List<MercenaryTaskModel>): MercenaryTaskModel? {
        return findAllMatchingTasks(standyMissions).firstOrNull()
    }
}